<?php

namespace App\Listeners;

use GuzzleHttp\Utils;
use Swof\Event\Listener;
use Swof\Http\WebSocketRequest;
use Swof\Server\Socket\WebSocketServer;
use Swoole\WebSocket\Server as SwoWsServer;
use Swoole\Coroutine\Http\Client;

class WsMessageBeforeListener extends Listener
{
    protected $name = 'ws.message.before';

    public function handle($args = [])
    {
        $wsServer = $args[0];
        $swoWsServer = $args[1];
        $frame = $args[2];

        $data = json_decode($frame->data, true);

        $this->{$data['method']}($wsServer, $swoWsServer, $data);
    }

    /**
     * 给 route 发送广播
     *
     * @param WebSocketServer $server
     * @param SwoWsServer $swoWsServer
     * @param array $data
     */
    protected function serverBroadcast(WebSocketServer $server, SwoWsServer $swoWsServer, array $data)
    {
        go(function () use ($server, $data) {
            $config = config('server.route');

            $client = new Client($config['host'], $config['port']);

            $ret = $client->upgrade('/');

            if ($ret) {
                $client->push(json_encode([
                    'method' => 'routeBroadcast',
                    'msg' => $data['msg']
                ]));
            }
        });
    }

    /**
     * 接受 route 服务器的广播信息
     *
     * @param WebSocketServer $server
     * @param SwoWsServer $swoWsServer
     * @param array $data
     */
    protected function routeBroadcast(WebSocketServer $server, SwoWsServer $swoWsServer, array $data)
    {
        $server->sendAll($data);
    }

    /**
     * 向 Route 发送私聊
     *
     * @param WebSocketServer $server
     * @param SwoWsServer $swoWsServer
     * @param array $data
     */
    protected function privateChat(WebSocketServer $server, SwoWsServer $swoWsServer, array $data)
    {
        $jwtConfig = config('server.route.jwt');

        $json = $server->getRedis()->hGet($jwtConfig['key'], $data['clientId']);
        $arr = json_decode($json, true);

        $request = WebSocketRequest::get($arr['fd'])['request'];
        $token = $request->header['sec-websocket-protocol'];

        go(function () use ($arr, $data, $token) {
            $server = explode(':', $arr['server_url']);

            $client = new Client('127.0.0.1', $server[1]);
            $client->setHeaders(['sec-websocket-protocol' => $token]);

            $ret = $client->upgrade('/');

            if ($ret) {
                $client->push(json_encode([
                    'msg' => $data['msg'],
                    'method' => 'forwarding',
                    'fd' => $arr['fd']
                ], 256));
            }
        });
    }

    /**
     * 转发私聊信息
     *
     * 六星教育 @shineyork老师
     * @param WebSocketServer $server
     * @param SwoWsServer $swoWsServer
     * @param $data
     */
    protected function forwarding(WebSocketServer $server, SwoWsServer $swoWsServer, $data)
    {
        $swoWsServer->push($data['fd'], json_encode(['msg' => $data['msg']]));
    }
}